package com.example.forumsystem.controller;


import com.example.forumsystem.common.AppResult;
import com.example.forumsystem.common.ResultCode;
import com.example.forumsystem.config.AppConfig;
import com.example.forumsystem.exception.ApplicationException;
import com.example.forumsystem.model.Message;
import com.example.forumsystem.model.User;
import com.example.forumsystem.services.impl.MessageServiceImpi;
import com.example.forumsystem.services.impl.UserServiceImpi;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiModelProperty;
import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiParam;
import lombok.NonNull;
import lombok.extern.slf4j.Slf4j;
import org.apache.coyote.http11.upgrade.UpgradeServletOutputStream;
import org.springframework.web.bind.annotation.*;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpSession;
import java.util.Date;
import java.util.List;

import static com.example.forumsystem.config.AppConfig.USER_SESSION;

@Slf4j
@RestController
@Api(tags = "站内信接口")
@RequestMapping("/message")
public class MessageController {

    @Resource
    private MessageServiceImpi messageServiceImpi;

    @Resource
    private UserServiceImpi userServiceImpi;

    @ApiOperation("创建站内信")
    @PostMapping("/send")
    public AppResult send(HttpServletRequest request ,
                          @ApiParam("接收者id") @RequestParam("receiveUserId") @NonNull Long receiveUserId,
                          @ApiParam("正文") @RequestParam("content") @NonNull String content) {
        // 获取登入user
        HttpSession session = request.getSession(false);
        User user = (User) session.getAttribute(USER_SESSION);
        // 校验发送者权限
        if(user == null || user.getState() == 1 || user.getDeleteState() == 1) {
            // 打印日志
            log.info(ResultCode.FAILED_USER_BANNED.toString());
            // 返回异常
            return AppResult.failed(ResultCode.FAILED_USER_BANNED);
        }

        // 校验接受者状态
        User receiveUser = userServiceImpi.selectById(receiveUserId);
        if(receiveUser == null || receiveUser.getState() == 1 || receiveUser.getDeleteState() == 1) {
            // 返回异常
            log.info("接受方不存在");
            return AppResult.failed("发送失败,请联系管理员!");
        }
        // 校验结收者是否为发送者
        if(user.getId() == receiveUserId) {
            return AppResult.failed("不能给自己发送站内信");
        }
        // 构建修改对象
        Message message = new Message();
        message.setPostUserId(user.getId());
        message.setReceiveUserId(receiveUserId);
        message.setContent(content);
        // 调用service
        messageServiceImpi.create(message);
        // 返回结果
        return AppResult.success();
    }
    @ApiOperation("/查询用户的所有站内信")
    @GetMapping("/getAll")
    public AppResult<List<Message>> getAll(HttpServletRequest request) {
        // 获取user对象
        HttpSession session = request.getSession(false);
        User user = (User) session.getAttribute(USER_SESSION);

        List<Message> result = messageServiceImpi.selectByReceiveUserId(user.getId());

        return AppResult.success(result);
    }

    @ApiOperation("获取用户站内信未读数")
    @GetMapping("/getUnreadCount")
    public AppResult getUnreadCount(HttpServletRequest request) {
        HttpSession session = request.getSession(false);
        User user = (User) session.getAttribute(USER_SESSION);

        Integer count = messageServiceImpi.selectUnreadCount(user.getId());

        return AppResult.success(count);
    }


    @ApiOperation("更新站内信为已读")
    @PostMapping("/markRead")
    public AppResult markRead(HttpServletRequest request,
                              @ApiParam("站内信id") @RequestParam("id") @NonNull Long id) {
        // 获取session
        HttpSession session = request.getSession(false);
        User user = (User) session.getAttribute(USER_SESSION);
        // 获取站内信
        Message message = messageServiceImpi.selectById(id);
        // 校验是否查看的是自己的
        if(message != null && user.getId() != message.getReceiveUserId()) {
            // 打印日志
            log.info("查询不属于自己的站内信, userId: " + user.getId() );
            // 返回异常
            return AppResult.failed(ResultCode.FAILED);
        }

        // 调用DAO
        messageServiceImpi.updateStateById(id, (byte) 1);
        // 返回结果
        return AppResult.success();
    }

    @PostMapping("/reply")
    @ApiOperation("回复站内信")
    public AppResult reply(HttpServletRequest request,
                           @ApiParam("站内信id") @RequestParam("repliedId") @NonNull Long repliedId,
                           @ApiParam("站内信内容") @RequestParam("content") @NonNull String content) {
        // 获取登入用户
        HttpSession session = request.getSession(false);
        User user = (User) session.getAttribute(AppConfig.USER_SESSION);


        // 根据站内信id,校验站内信对象
        Message existsMessage = messageServiceImpi.selectById(repliedId);
        if (existsMessage == null || existsMessage.getDeleteState() == 1) {
            log.info(ResultCode.FAILED_MESSAGE_NOT_EXISTS.toString());
            // 抛异常
            throw new ApplicationException(AppResult.failed(ResultCode.FAILED_MESSAGE_NOT_EXISTS));
        }

        // 检测是否重复回复
        if(existsMessage.getState() == 2) {
            throw new ApplicationException("该站内信你已经回复过了");
        }

        // 校验接受者
        if(user.getId() == existsMessage.getPostUserId()) {
            throw new ApplicationException(AppResult.failed("不能给回复自己的站内信"));
        }

        // 初始化对象
        Message updateMessage = new Message();
        updateMessage.setPostUserId(user.getId()); // 发送者
        updateMessage.setReceiveUserId(existsMessage.getPostUserId()); // 接收者
        updateMessage.setContent(content); // 正文
        Date date = new Date();
        updateMessage.setUpdateTime(date);
        updateMessage.setCreateTime(date);
        // 调用service
        messageServiceImpi.reply(repliedId,updateMessage);
        // 返回结果
        return AppResult.success();
    }
}

